#include <p18cxxx.h>

#ifndef ISJFK_IR_MAIN
#define ISJFK_IR_MAIN

#define OSC_FEQ             10000000        // 10Mhz Osc
#define SERIAL_BAUD         9600            // serial port baud rate

#define BEGIN_TIME          2000            // signal begin low time, 2000ns
#define END_TIME            9000            // signal end high time, 9000ns
#define BIT_BEGIN_TIME      300             // bit begin time, 300ns
#define BIT_1_TIME          1120            // bit 1 high time, 1120ns
#define MAX_BYTE            16              // max byte stored

#define INS_FEQ             (OSC_FEQ / 4)   // instruction execution cycles per second
#define time2count(time)    (INS_FEQ / 1000 * time / 1000)

#define BEGIN_COUNT         time2count(BEGIN_TIME)
#define END_COUNT           time2count(END_TIME)
#define BIT_BEGIN_COUNT     time2count(BIT_BEGIN_TIME)
#define BIT_1_COUNT         time2count(BIT_1_TIME)

#define USART_BRG           (INS_FEQ / SERIAL_BAUD - 1)
#define TIMER_INIT_VAL      (~(END_COUNT - 1))

#define STATE_WAIT_SIG      0
#define STATE_SIG_HEAD1     1
#define STATE_SIG_HEAD2     2
#define STATE_IN_SIG        3

// system parameters
union {
    struct {
        unsigned writeLen   : 1;    // write signal length before write signal to serial port?
        unsigned none       : 7;
    };
    unsigned char byte;
} params;

unsigned char state;            // state machine

void main(void);
void init(void);

void onSigHead(void);
void onSigStart(void);
void onSigBitRecv(unsigned char b);
void onSigEndSuccess(void);
void onSigEndError(void);

void putByteUSART(unsigned char byte);
void InterruptHandlerHigh(void);

#define getTimer0Count()    (ReadTimer0() - TIMER_INIT_VAL)

#define isIrInIntOnHigh()   INTCON2bits.INTEDG1
#define isIrInIntOnLow()    !INTCON2bits.INTEDG1
#define setIrInIntOnHigh()  INTCON2bits.INTEDG1 = 1
#define setIrInIntOnLow()   INTCON2bits.INTEDG1 = 0
#define isIrInInt()         INTCON3bits.INT1IF
#define clrIrInInt()        INTCON3bits.INT1IF = 0
#define isIrInHigh()        PORTBbits.RB1
#define isIrInLow()         !PORTBbits.RB1

#define isTimer0Int()       INTCONbits.TMR0IF
#define clrTimer0Int()      INTCONbits.TMR0IF = 0

#endif